<?php
namespace app\index\model;

use app\common\model\SuperModel;
use app\common\sdk\PassHash;
use app\index\model\Role;
use think\Session;
use traits\model\SoftDelete;


class User extends SuperModel
{
    /**
     * 软删除固定写法
     */
    use SoftDelete;
    protected $deleteTime = 'delete_time';
    protected $updateTime = false;

    /**
     * @const  用户账号状态
     */
    const BANNED = 0; //封禁账号
    const NORMAL = 1; //正常账号

    /**
     * 加密密钥
     *
     * @var string
     */
    private $key = 'key';


    /**
     * 用户-角色关联定义
     * @return   object
     */
    public function role()
    {

        //角色HAS ONE账号关联
        //
        return $this->hasOne('Role', 'role_id', 'id');
    }

    /**
     * 加密修改器
     *
     * @param  string $pass 被加密口令
     */
    public function setPassAttr($pass)
    {
        return PassHash::authcode($pass, 'ENCODE', $this->key);
    }

    //======================================================/

    /**
     * 登录认证
     *
     * @param  string  $username 用户名
     * @param  string  $password 用户密码
     * @return integer 登录成功-用户ID，登录失败-返回0或-1
     */
    public function login($username, $password)
    {
        try {

            $user = self::getByUser($username);

            if ($user) {

                if (self::BANNED == $user->status) {

                    $output = array('success' => false, 'msg' => "账号已锁定,请联系管理员！");
                    $this->doLog($output, false); //非授权日志

                    return $output;

                }
                if ($password == PassHash::authcode($user['pass'], 'DECODE', $this->key)) {

                    //登录次数计数自增
                    //
                    $user->setInc('login_times');

                    //登录失败次数清零
                    //
                    $this->clearLoginFailure($username);

                    $info = $user->getData();

                    //销毁口令

                    unset($info['pass']);

                    //添加角色信息

                    $role = Role::get($user->role_id);

                    $info['role_name'] = $role->getData('role_name');
                    $info['role_menus'] = $role->getData('menu_ids');

                    //设置当前用户会话变量
                    //
                    Session::set('CURRENT_USER', $info);

                    $output = array('success' => true, 'msg' => "登录成功！", 'data' => $info);
                    $this->doLog($output);

                    return $output;

                } else {

                    $this->countLoginFailure($username);

                    $output = array('success' => false, 'msg' => "用户名或密码错误！");
                    $this->doLog($output, false); //非授权

                    return $output;

                }
            } else {

                $this->countLoginFailure($username);

                $output = array('success' => false, 'msg' => "用户名或密码错误！");
                $this->doLog($output, false); //非授权

                return $output;

            }
        } catch (\Exception $e) {

            $output = array('success' => false, 'msg' => $e->getMessage());
            $this->doLog($output, false); //非授权

            return $output;

        }
    }
    /**
     * 登录失败计数清零
     * @param  string  $usename 用户登录账号
     */
    public function clearLoginFailure($username)
    {
        Session::set('login_failures', 0);
    }
    /**
     * 登录失败计数
     * @param  string  $usename 用户登录账号
     */
    public function countLoginFailure($username)
    {

        try {
            if (Session::has('login_failures')) {

                // 5次超限判断

                if (Session::get('login_failures') >= 5) {

                    $this->where('user', $username)->update(['status' => 2]);

                    //系统用户封禁记录
                    $this->banUserAccount($username);

                    //返回提示信息
                    $output = array('success' => false, 'msg' => "用户名或密码错误次数超限！");
                    $this->doLog($output, false); //非授权

                    _callback($output);

                } else {
                    $count = Session::get('login_failures');
                    Session::set('login_failures', $count + 1);
                }
            } else {
                Session::set('login_failures', 1);
            }
        } catch (\Exception $e) {

            $output = array('success' => false, 'msg' => $e->getMessage());
            $this->doLog($output, false); //非授权

            throw new \think\Exception('异常消息:' . $e->getMessage());
        }
    }
    /**
     * 用户列表
     * @return   void
     */
    public function doList($param = null)
    {

        try {

            //记录总计
            $total = $this->where('status', 'in', '1,2')
                ->count();

            //查询排序

            $list = $this->join('role', 'user.role_id = role.id')
                ->where('status', 'in', '1,2')
                ->field('user.id,user.cname,user.pass,user.create_time,user.update_time,user.status,user.user,user.role_id,role.role_name')
                ->order('user.id asc')
                ->select();

            $rows = [];

            foreach ($list as $data) {
                $item = $data->getData();
                array_push($rows, $item);
            }

            $res = array();

            // 解密
            if ($total > 0) {
                foreach ($rows as $key => $value) {
                    $rows[$key]['pass'] = PassHash::authcode($value['pass'], 'DECODE', $this->key);
                }
                $res['rows'] = $rows;
                $res['total'] = $total;
            } else {
                $res['total'] = 0;
                $res['rows'] = array();
            }

            return $res;

        } catch (\Exception $e) {

            $output = array(
                'success' => false,
                'msg' => $e->getMessage(),
            );

            throw new \think\Exception('异常消息:' . $e->getMessage());
        }
    }

    /**
     * 修改密码
     *
     * @param    string $user 用户名
     * @param    string $oldpass 旧密码
     * @param    string $newpass 新密码
     * @return   void
     */
    public function doChangePass($user, $oldpass, $newpass)
    {

        try {

            $user = self::getByUser($user);

            //旧密码验证

            if ($oldpass == PassHash::authcode($user['pass'], 'DECODE', $this->key)) {

                //修改内容

                $changeData['pass'] = $newpass;
                $changeData['update_time'] = date("Y-m-d H:i:s");

                //更新数据

                $res = $user->allowField(true)
                    ->isUpdate(true)
                    ->save($changeData);

                //返回信息

                $output = array('success' => $res ? true : false, 'msg' => $res ? "更新成功！" : "更新失败！", 'data' => $res);
                $this->doLog($output);

                return $output;

            } else {

                $output = array('success' => false, 'msg' => "旧密码错误");
                $this->doLog($output);

                return $output;

            }
        } catch (\Exception $e) {

            throw new \think\Exception('异常消息:' . $e->getMessage());

            $output = array('success' => false, 'msg' => $e->getMessage());
            $this->doLog($output);
        }
    }

    /**
     * 用户登出
     */
    public function doLogout()
    {

        $output = array('success' => true, 'msg' => "退出成功！");

        if (Session::has('CURRENT_USER')) {
            $this->doLog($output);
        } else {
            $this->doLog($output, false); //非授权日志记录
        }

        //清空会话
        session(null);

        return $output;
    }
    /**
     * 账户封禁
     */
    public function banUserAccount($user)
    {

        $id = $user;
        $reason = '密码输入错误次数超限';

        $newstamp = strtotime('+ 10 minutes');
        $deadline = date('Y-m-d H:i:s', $newstamp);

    }
}
